package edu.njust.cma.service.impl;

import edu.njust.cma.DTO.ExtraTask;
import edu.njust.cma.DTO.LabTaskJson;
import edu.njust.cma.pojo.SubtaskAdditionalRequirement;
import edu.njust.cma.pojo.SubtaskFacilityComparisonInspect;
import edu.njust.cma.DTO.TaskDecomposeRequestJSON;
import edu.njust.cma.config.ConstantConfig;
import edu.njust.cma.mapper.*;
import edu.njust.cma.pojo.*;
import edu.njust.cma.service.TaskService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Service
public class TaskServiceImpl implements TaskService {



    @Override
    public List<Task> getTask(Integer smallProjectId) {
        return taskMapper.getTask(smallProjectId);
    }

    @Override
    public Map<SubtaskStaff, User> getStaffTask(Integer taskId) {
        List<SubtaskStaff> list = subtaskStaffMapper.getStaffTask(taskId);
        Map<SubtaskStaff, User> map = new HashMap<>();
        for (SubtaskStaff subtaskStaff : list) {
            var user = userMapper.getUserInfo(subtaskStaff.getStaffId());
            map.put(subtaskStaff, user);
        }
        return map;
    }

    @Override
    public Map<SubtaskEquipment, Equipment> getSubtaskEquipment(Integer taskId) {
        List<SubtaskEquipment> list = subtaskEquipmentMapper.getSubtaskEquipment(taskId);
        Map<SubtaskEquipment, Equipment> map = new HashMap<>();
        for (SubtaskEquipment subtaskEquipment : list) {
            Equipment equipment = equipmentMapper.getEquipment(subtaskEquipment.getEquipmentId());
            map.put(subtaskEquipment, equipment);
        }
        return map;
    }

    @Override
    public SubtaskSample getSubtaskSample(Integer taskId) {
        return subtaskSampleMapper.getSubtaskSample(taskId);
    }

    @Override
    public List<SubtaskAdditionalRequirement> getSubtaskAdditionalRequirement(Integer taskId) {
        return subtaskAdditionalRequirementMapper.getSubtaskAdditionalRequirement(taskId);
    }

    @Override
    public SubtaskFacilityComparisonInspect getSubtaskFacility(Integer taskId) {
        return subtaskFacilityComparisonInspectMapper.getSubtaskByTaskIdAndType(taskId, ConstantConfig.FACILITIES);
    }

    @Override
    public SubtaskFacilityComparisonInspect getSubtaskComparison(Integer taskId) {
        return subtaskFacilityComparisonInspectMapper.getSubtaskByTaskIdAndType(taskId, ConstantConfig.COMPARISON);
    }

    @Override
    public SubtaskFacilityComparisonInspect getSubtaskInspect(Integer taskId) {
        return subtaskFacilityComparisonInspectMapper.getSubtaskByTaskIdAndType(taskId, ConstantConfig.INSPECT);
    }

    @Override
    public SubtaskSimulation getSubtaskSimulation(Integer taskId) {
        return subTaskSimulationMapper.getSubtaskSimulation(taskId);
    }

    @Override
    public Boolean decomposeTask(TaskDecomposeRequestJSON taskDecomposeRequestJSON) {
        // 1. 插入人员任务
        for (Integer staffId : taskDecomposeRequestJSON.getSubtaskStaffIds()) {
            SubtaskStaff subtaskStaff = new SubtaskStaff();
            subtaskStaff.setTaskId(taskDecomposeRequestJSON.getTaskId());
            subtaskStaff.setStaffId(staffId);
            subtaskStaff.setUserId(taskDecomposeRequestJSON.getSubtaskStaffUserId());
            subtaskStaffMapper.insert(subtaskStaff);
        }
        // 2. 插入设备任务
        for (Integer equipmentId : taskDecomposeRequestJSON.getSubtaskEquipmentIds()) {
            SubtaskEquipment subtaskEquipment = new SubtaskEquipment();
            subtaskEquipment.setTaskId(taskDecomposeRequestJSON.getTaskId());
            subtaskEquipment.setEquipmentId(equipmentId);

            subtaskEquipmentMapper.insert(subtaskEquipment);

        }
        // 3. 插入样品任务
        SubtaskSample subtaskSample = new SubtaskSample();
        subtaskSample.setTaskId(taskDecomposeRequestJSON.getTaskId());
        subtaskSample.setSampleName(taskDecomposeRequestJSON.getSampleName());
        subtaskSample.setSampleModel(taskDecomposeRequestJSON.getSampleModel());
        subtaskSample.setBatchNumber(taskDecomposeRequestJSON.getBatchNumber());
        subtaskSample.setSampleManagerId(taskDecomposeRequestJSON.getSampleManagerId());
        subtaskSample.setUserId(taskDecomposeRequestJSON.getSubtaskSampleUserId());
        subtaskSampleMapper.insert(subtaskSample);
        // 4. 插入额外任务
        for (ExtraTask extraTask : taskDecomposeRequestJSON.getSubtaskAdditions()) {
            SubtaskAdditionalRequirement subtaskAdditionalRequirement = new SubtaskAdditionalRequirement();
            subtaskAdditionalRequirement.setTaskId(taskDecomposeRequestJSON.getTaskId());
            subtaskAdditionalRequirement.setRequirementName(extraTask.getName());
            subtaskAdditionalRequirement.setRequirementContent(extraTask.getContent());
            subtaskAdditionalRequirement.setUserId(extraTask.getSubtaskExtraUserId());
            subtaskAdditionalRequirementMapper.insert(subtaskAdditionalRequirement);
        }
        // 5. 插入设施任务
        if (taskDecomposeRequestJSON.getIsFacilityTask()) {
            SubtaskFacilityComparisonInspect subtaskFacility = new SubtaskFacilityComparisonInspect();
            subtaskFacility.setTaskId(taskDecomposeRequestJSON.getTaskId());
            subtaskFacility.setUserId(taskDecomposeRequestJSON.getSubtaskFacilityUserId());
            subtaskFacilityComparisonInspectMapper.create(subtaskFacility.getTaskId(), subtaskFacility.getUserId(), ConstantConfig.FACILITIES);
        }
        // 6. 插入对比任务
        if (taskDecomposeRequestJSON.getIsComparisonTask()) {
            SubtaskFacilityComparisonInspect subtaskComparison = new SubtaskFacilityComparisonInspect();
            subtaskComparison.setTaskId(taskDecomposeRequestJSON.getTaskId());
            subtaskComparison.setUserId(taskDecomposeRequestJSON.getSubtaskComparisonUserId());
            subtaskFacilityComparisonInspectMapper.create(subtaskComparison.getTaskId(),
                    subtaskComparison.getUserId(), ConstantConfig.COMPARISON);
        }
        // 7. 插入检查任务
        SubtaskFacilityComparisonInspect subtaskInspect = new SubtaskFacilityComparisonInspect();
        subtaskInspect.setTaskId(taskDecomposeRequestJSON.getTaskId());
        subtaskInspect.setUserId(taskDecomposeRequestJSON.getSubtaskInspectUserId());
        subtaskFacilityComparisonInspectMapper.create(subtaskInspect.getTaskId(), subtaskInspect.getUserId(), ConstantConfig.INSPECT);
        // 8. 插入模拟任务
        SubtaskSimulation subtaskSimulation = new SubtaskSimulation();
        subtaskSimulation.setTaskId(taskDecomposeRequestJSON.getTaskId());
        subtaskSimulation.setUserId(taskDecomposeRequestJSON.getSubtaskSimulationUserId());
        subTaskSimulationMapper.insert(subtaskSimulation);
        // 修改状态为未完成
        taskMapper.updateStatus(taskDecomposeRequestJSON.getTaskId(), ConstantConfig.UNFINISHED);
        return true;
    }

    @Override
    public void checkTaskPass(Submission submission) {
        int submissionId ;
        if(submission.getType() == ConstantConfig.STAFF_SubTASK){
            submissionId = submissionmapper.getSubmissionIdByTaskId(submission.getTaskId(),submission.getType());}
        else
         submissionId = submissionmapper.getSubmissionIdBySubTaskId(submission.getSubtaskId(),submission.getType());
        // 修改提交的状态
        submissionmapper.updateStatusById(submissionId, ConstantConfig.PASS);
        // 修改提交的评语
        submissionmapper.updateFeedbackById(submissionId, submission.getFeedback());

        /**
         * 先判断这个提交为什么类型的任务，修改对应的任务状态
         */
        switch (submission.getType()) {
            case ConstantConfig.STAFF_SubTASK:
                // 修改人员任务状态
                subtaskStaffMapper.updateStatusByTaskId(submission.getTaskId(), ConstantConfig.PASS);
                break;
            case ConstantConfig.EQUIPMENT_SubTASK:

                break;
            case ConstantConfig.SAMPLE_SubTASK:
                // 修改样品任务状态
                subtaskSampleMapper.updateStatus(submission.getSubtaskId(), ConstantConfig.PASS);
                break;
            case ConstantConfig.ADDITIONAL_SubTASK:
                // 修改额外任务状态
                subtaskAdditionalRequirementMapper.updateStatusById(submission.getSubtaskId(), ConstantConfig.PASS);
                break;
            case ConstantConfig.FACILITY_SubTASK:
                // 修改设施任务状态
                subtaskFacilityComparisonInspectMapper.updateStatus(submission.getSubtaskId(), ConstantConfig.PASS, ConstantConfig.FACILITIES);
                break;
            case ConstantConfig.COMPARISON_SubTASK:
                // 修改对比任务状态
                subtaskFacilityComparisonInspectMapper.updateStatus(submission.getSubtaskId(), ConstantConfig.PASS, ConstantConfig.COMPARISON);
                break;
            case ConstantConfig.INSPECT_SubTASK:
                // 修改检查任务状态
                subtaskFacilityComparisonInspectMapper.updateStatus(submission.getSubtaskId(), ConstantConfig.PASS, ConstantConfig.INSPECT);
                break;
            case ConstantConfig.SIMULATION_SubTASK:
                // 修改模拟任务状态
                subTaskSimulationMapper.updateStatus(submission.getSubtaskId(), ConstantConfig.PASS);
                break;
        }

        // 检查任务状态是否需要修改为完成
        boolean flag = true;
        // 获取所有的人员任务状态
        List<Integer> staffTaskStatus = subtaskStaffMapper.getStatusByTaskId(submission.getTaskId());

        for (Integer st : staffTaskStatus) {
            flag &= st == ConstantConfig.PASS;
        }

        // 获取所有的样品任务状态
        flag &= subtaskSampleMapper.getStatus(submission.getTaskId()) == ConstantConfig.PASS;

        List<Integer> additionalRequirementMapperStatus = subtaskAdditionalRequirementMapper.getStatusByTaskId(submission.getSubtaskId());
        for (Integer st : additionalRequirementMapperStatus) {
            flag &= st == ConstantConfig.PASS;
        }

        // 如果有设施任务，需要判断设施任务是否通过
        if (subtaskFacilityComparisonInspectMapper.getSubtaskCountByTaskId(submission.getTaskId(), ConstantConfig.FACILITIES) != 0) {
            flag &= subtaskFacilityComparisonInspectMapper.getStatusByTaskIdAndType(submission.getTaskId(), ConstantConfig.FACILITIES) == ConstantConfig.PASS;
        }
        // 如果有对比任务，需要判断对比任务是否通过
        if (subtaskFacilityComparisonInspectMapper.getSubtaskCountByTaskId(submission.getTaskId(), ConstantConfig.COMPARISON) != 0) {
            flag &= subtaskFacilityComparisonInspectMapper.getStatusByTaskIdAndType(submission.getTaskId(), ConstantConfig.COMPARISON) == ConstantConfig.PASS;
        }
        if(flag==false) System.out.println("no1");
        flag &=
                subtaskFacilityComparisonInspectMapper.
                        getStatusByTaskIdAndType(submission.getTaskId(), ConstantConfig.INSPECT) == ConstantConfig.PASS;
        if(flag==false) System.out.println("no2");

        flag &= subTaskSimulationMapper.getStatus(submission.getTaskId()) == ConstantConfig.PASS;
        if (flag) {
            taskMapper.updateStatus(submission.getTaskId(), ConstantConfig.FINISHED);
        }

        // 检查项目状态是否需要修改为完成
        flag = true;

        Integer projectId = taskMapper.getProjectIdByTaskId(submission.getTaskId());

        List<Integer> taskStatus = taskMapper.getStatusByProjectId(projectId);

        for (Integer st : taskStatus) {
            flag &= st == ConstantConfig.FINISHED;
        }
        if(flag) {
            projectMapper.updateStatus(projectId, ConstantConfig.FINISHED);
        }

    }

    @Override
    public void checkTaskFail(Submission submission) {
        int submissionId = submissionmapper.getSubmissionIdByTaskId(
                submission.getTaskId(),submission.getType()
        );
        // 修改提交的状态
        submissionmapper.updateStatusById(submissionId, ConstantConfig.NOT_PASS);
        // 修改提交的评语
        submissionmapper.updateFeedbackById(submissionId, submission.getFeedback());
    }
    /**
     * 获取所有未分解的任务
     * @param userId
     * @return
     */
    @Override
    public List<LabTaskJson> getTasksUnDecompose(int userId) {
        List<LabTaskJson> list = new ArrayList<>();
        /**
         * 通过userId获取到自己所有的项目
         * 在通过项目获取到子项目
         * 在通过子项目获取到任务
         * 通过子项目获取到子项目的标准名称
         * 创建LabTaskJson对象 将项目名字 标准名称 任务名称 任务传入
         * */
        List<Project> projects = projectMapper.getProjectByLabHeadId(userId);
        for (Project project : projects) {
            List<SmallProject> smallProjects = smallProjectMapper.getSmallProjectByProjectId(project.getId());
            for (SmallProject smallProject : smallProjects) {
                List<Task> tasks = taskMapper.getTaskBySmallProjectId(smallProject.getId());

                String standardName = standardMapper.getStandardById(smallProject.getStandardId()).getName();

                for (Task task : tasks) {
                    if(task.getStatus()!=ConstantConfig.UN_DECOMPOSED){
                        continue;
                    }
                    LabTaskJson labTaskJson = new LabTaskJson(project.getName(), standardName, task.getName(), task,null);
                    list.add(labTaskJson);
                }

            }
        }
        return list;
    }

    /**
     * 获取所有未提交的任务
     * @param labHeadUserId
     * @return
     */
    @Override
    public List<LabTaskJson> getTasksUnSubmit(int labHeadUserId) {
        List<LabTaskJson> list = new ArrayList<>();
        /**
         * 通过userId获取到自己所有的项目
         * 在通过项目获取到子项目
         * 在通过子项目获取到任务
         * 通过子项目获取到子项目的标准名称
         * 创建LabTaskJson对象 将项目名字 标准名称 任务名称 任务传入
         * */
        List<Project> projects = projectMapper.getProjectByLabHeadId(labHeadUserId);
        for (Project project : projects) {
            List<SmallProject> smallProjects = smallProjectMapper.getSmallProjectByProjectId(project.getId());
            for (SmallProject smallProject : smallProjects) {
                List<Task> tasks = taskMapper.getTaskBySmallProjectId(smallProject.getId());
                String standardName = standardMapper.getStandardById(smallProject.getStandardId()).getName();
                for (Task task : tasks) {
                    if(task.getStatus()!=ConstantConfig.UNFINISHED){
                        continue;
                    }
                    // 获取状态未
                    if(submissionmapper.getUncheckSubmissionCountByTaskId(task.getId()) >= 1){
                        continue;
                    }
                    LabTaskJson labTaskJson = new LabTaskJson(project.getName(), standardName, task.getName(), task,null);
                    list.add(labTaskJson);
                }
            }
        }
        return list;
    }

    /**
     * 获取所有未审核的任务
     * @param labHeadUserId
     * @return
     */
    @Override
    public List<LabTaskJson> getsTasksUnCheck(int labHeadUserId) {
        List<LabTaskJson> list = new ArrayList<>();
        /**
         * 通过userId获取到自己所有的项目
         * 在通过项目获取到子项目
         * 在通过子项目获取到任务
         * 通过子项目获取到子项目的标准名称
         * 创建LabTaskJson对象 将项目名字 标准名称 任务名称 任务传入
         * */
        List<Project> projects = projectMapper.getProjectByLabHeadId(labHeadUserId);
        for (Project project : projects) {
            List<SmallProject> smallProjects = smallProjectMapper.getSmallProjectByProjectId(project.getId());
            for (SmallProject smallProject : smallProjects) {
                List<Task> tasks = taskMapper.getTaskBySmallProjectId(smallProject.getId());
                String standardName = standardMapper.getStandardById(smallProject.getStandardId()).getName();
                for (Task task : tasks) {
                    if(task.getStatus()!=ConstantConfig.UNFINISHED){
                        continue;
                    }
                    if(submissionmapper.getUncheckSubmissionCountByTaskId(task.getId()) == 0){
                        continue;
                    }
                    LabTaskJson labTaskJson = new LabTaskJson(project.getName(), standardName, task.getName(), task,null);
                    list.add(labTaskJson);
                }
            }
        }
        return list;
    }

    /**
     * 获取所有已经完成的任务
     * @param labHeadUserId
     * @return
     */
    @Override
    public List<LabTaskJson> getTasksFinished(int labHeadUserId) {
        List<LabTaskJson> list = new ArrayList<>();
        /**
         * 通过userId获取到自己所有的项目
         * 在通过项目获取到子项目
         * 在通过子项目获取到任务
         * 通过子项目获取到子项目的标准名称
         * 创建LabTaskJson对象 将项目名字 标准名称 任务名称 任务传入
         * */
        List<Project> projects = projectMapper.getProjectByLabHeadId(labHeadUserId);
        for (Project project : projects) {
            List<SmallProject> smallProjects = smallProjectMapper.getSmallProjectByProjectId(project.getId());
            for (SmallProject smallProject : smallProjects) {
                List<Task> tasks = taskMapper.getTaskBySmallProjectId(smallProject.getId());

                String standardName = standardMapper.getStandardById(smallProject.getStandardId()).getName();

                for (Task task : tasks) {
                    if(task.getStatus()!=ConstantConfig.FINISHED){
                        continue;
                    }
                    LabTaskJson labTaskJson = new LabTaskJson(project.getName(), standardName, task.getName(), task,null);
                    list.add(labTaskJson);
                }

            }
        }
        return list;
    }

    @Override
    public SubtaskAdditionalRequirement getSubtaskAdditionalRequirementBySubtaskId(Integer subtaskId) {
        return subtaskAdditionalRequirementMapper.getSubtaskAdditionalRequirementById(subtaskId);
    }

    @Autowired
    SmallProjectMapper smallProjectMapper;
    @Autowired
    TaskMapper taskMapper;
    @Autowired
    SubtaskStaffMapper subtaskStaffMapper;
    @Autowired
    UserMapper userMapper;
    @Autowired
    SubtaskEquipmentMapper subtaskEquipmentMapper;
    @Autowired
    EquipmentMapper equipmentMapper;
    @Autowired
    SubtaskSampleMapper subtaskSampleMapper;
    @Autowired
    SubtaskFacilityComparisonInspectMapper subtaskFacilityComparisonInspectMapper;
    @Autowired
    SubtaskAdditionalRequirementMapper subtaskAdditionalRequirementMapper;
    @Autowired
    SubTaskSimulationMapper subTaskSimulationMapper;

    @Autowired
    SubmissionMapper submissionmapper;
    @Autowired
    ProjectMapper projectMapper;

    @Autowired
    StandardMapper standardMapper;

}

